<template>
    <el-input
        v-if="item.ui === UIName.input"
        :ref="forwardRef"
        v-model="state.form[item.key]"
        :clearable="item.clearable"
        :type="item.type"
        :disabled="isFunc(item.disabled) ? item.disabled({ form: state.form , initData: props.initData, item}) : item.disabled"
        :maxlength="item.maxlength"
        :minlength="item.minlength"
        :show-word-limit="item.showWordLimit"
        :prefix-icon="item.prefixIcon"
        :suffix-icon="item.suffixIcon"
        :rows="item.rows"
        :autosize="item.autosize"
        :placeholder="item.placeholder || _placeholder || ''"
        :spellcheck="false"
        style="width: 100%;"
        @change="() => handleEvent({item, eventName: 'change'})"
        @blur="() => handleEvent({item, eventName: 'blur'})"
        @input="() => handleEvent({item, eventName: 'input'})">
    </el-input>
    <InputLink
        v-if="item.ui === UIName.inputLink"
        v-model="state.form[item.key]"
        @leave="() => handleEvent({item, eventName: 'blur'})">
    </InputLink>
    <CellTextarea
        v-if="item.ui === UIName.cellTextarea"
        v-model="state.form[item.key]"
        :width="item.width"
        @leave="() => handleEvent({item, eventName: 'blur'})">
    </CellTextarea>
    <CellRichEditor
        v-if="item.ui === UIName.cellRichEditor"
        v-model="state.form[item.key]"
        @leave="() => handleEvent({item, eventName: 'blur'})">
    </CellRichEditor>
    <CellUpload
        v-if="item.ui === UIName.cellUpload"
        v-model="state.form[item.key]"
        :form="state.form"
        :width="item.width"
        @leave="() => handleEvent({item, eventName: 'blur'})">
    </CellUpload>
    <div
        v-else-if="item.ui === UIName.checkbox"
        :style="{padding: checkboxPadding ? '0 10px' : '0'}">
        <el-checkbox
            :ref="forwardRef"
            v-model="state.form[item.key]"
            @change="() => handleEvent({item, eventName: 'change'})">
        </el-checkbox>
    </div>
    <el-select
        v-else-if="item.ui === UIName.select"
        :ref="forwardRef"
        v-model="state.form[item.key]"
        :clearable="item.clearable"
        :placeholder="item.placeholder || _placeholder || ''"
        :disabled="isFunc(item.disabled) ? item.disabled({ form: state.form , initData: props.initData, item }) : item.disabled"
        :multiple="item.multiple"
        :collapse-tags="item.multiple"
        style="width: 100%;"
        @blur="() => handleEvent({item, eventName: 'blur'})"
        @change="() => handleEvent({item, eventName: 'change'})">
        <el-option
            v-for="(_item, _index) in item.dict && isFunc(item.dict.data) ? item.dict.data({ form: state.form , initData: props.initData}) : item.dict ? item.dict.data : []"
            :key="_index"
            :label="item.dict.labelKey ? _item[item.dict.labelKey] : _item.label"
            :value="item.dict.valueKey ? _item[item.dict.valueKey] : _item.value">
        </el-option>
    </el-select>
    <el-select
        v-else-if="item.ui === UIName.selectRemote"
        v-model="state.form[item.key]"
        :multiple="item.multiple"
        :clearable="item.clearable"
        :disabled="isFunc(item.disabled) ? item.disabled({ form: state.form , initData: props.initData, item }) : item.disabled"
        filterable
        remote
        reserve-keyword
        :placeholder="item.placeholder || _placeholder || ''"
        :remote-method="($event: any) => item.remoteMethod($event, initData)"
        :loading="item.loading"
        style="width: 100%"
        @change="() => handleEvent({item, eventName: 'change'})">
        <el-option
            v-for="(_item, _index) in item.dict && isFunc(item.dict.data) ? item.dict.data({ form: state.form , initData: props.initData}) : []"
            :key="_index"
            :label="item.dict.labelKey ? _item[item.dict.labelKey] : _item.label"
            :value="item.dict.valueKey ? _item[item.dict.valueKey] : _item.value">
        </el-option>
    </el-select>
    <el-date-picker
        v-else-if="[UIName.daterange, UIName.datetimerange].includes(item.ui)"
        :ref="forwardRef"
        v-model="state.form[item.key]"
        :type="item.ui"
        :clearable="item.clearable"
        :disabled="isFunc(item.disabled) ? item.disabled({ form: state.form , initData: props.initData, item }) : item.disabled"
        :value-format="item.valueFormat"
        :start-placeholder="item.startPlaceholder"
        :end-placeholder="item.endPlaceholder"
        style="width: 100%;"
        @blur="() => handleEvent({item, eventName: 'blur'})"
        @change="() => handleEvent({item, eventName: 'change'})">
    </el-date-picker>
    <el-date-picker
        v-else-if="[UIName.date, UIName.datetime].includes(item.ui)"
        :ref="forwardRef"
        v-model="state.form[item.key]"
        :type="item.ui"
        :placeholder="item.placeholder || _placeholder || ''"
        :clearable="item.clearable"
        :disabled="isFunc(item.disabled) ? item.disabled({ form: state.form , initData: props.initData, item }) : item.disabled"
        :value-format="item.valueFormat"
        style="width: 100%;"
        @blur="() => handleEvent({item, eventName: 'blur'})"
        @change="() => handleEvent({item, eventName: 'change'})">
    </el-date-picker>
    <el-input-number
        v-else-if="item.ui === UIName.inputNumber"
        :ref="forwardRef"
        v-model="state.form[item.key]"
        :controls="item.controls"
        :placeholder="item.placeholder || _placeholder || ''"
        :disabled="isFunc(item.disabled) ? item.disabled({ form: state.form , initData: props.initData, item }) : item.disabled"
        :style="{width: '100%'}"
        :class="[item.controls === false ? 'textAlignLeft' : '']"
        @blur="() => handleEvent({item, eventName: 'blur'})"
        @change="() => handleEvent({item, eventName: 'change'})">
    </el-input-number>
    <el-button
        v-else-if="item.ui === UIName.button"
        :title="item.circle ? item.label : ''"
        :type="item.type"
        :icon="isFunc(item.icon) ? item.icon({ form: state.form , initData: props.initData}): item.icon"
        :loading="item.loading"
        :circle="item.circle"
        @click="() => handleEvent({item, eventName: 'click'})">
        <template v-if="item.label && !item.circle" #default>
            {{ isFunc(item.label) ? item.label({ form: state.form , initData: props.initData}): item.label}}
        </template>
    </el-button>
    <template v-else-if="item.ui === UIName.buttonGroup">
        <el-button
            v-for="(_item, index) in item.children.filter((item: any) => isFunc(item.hide) ? !item.hide({ form: state.form , initData: props.initData}) : [undefined, false].includes(item.hide))"
            :key="index"
            :link="item.link"
            :type="isFunc(_item.type) ? _item.type({ form: state.form , initData: props.initData}): _item.type"
            :icon="isFunc(_item.icon) ? _item.icon({ form: state.form , initData: props.initData}): _item.icon"
            :disabled="isFunc(_item.disabled) ? _item.disabled({ form: state.form , initData: props.initData, item }) : _item.disabled"
            :size="_item.size"
            :loading="_item.loading"
            @click="() => handleEvent({item: _item, eventName: 'click'})">
            {{ isFunc(_item.label) ? _item.label({ form: state.form , initData: props.initData}): _item.label }}
        </el-button>
    </template>
    <template v-else-if="item.ui === UIName.tab">
        <el-tabs
            v-model="state.form[item.key]"
            @tab-click="($event: any) => {state.form[item.key]=$event.props.name;handleEvent({item, eventName: 'click'})}">
            <el-tab-pane
                v-for="(_item, _index) in item.dict && isFunc(item.dict.data) ? item.dict.data({ form: state.form , initData: props.initData}) : item.dict ? item.dict.data : []"
                :key="_index"
                :label="item.dict.labelKey ? _item[item.dict.labelKey] : _item.label"
                :name="item.dict.valueKey ? _item[item.dict.valueKey] : _item.value">
            </el-tab-pane>
        </el-tabs>
    </template>
    <div
        v-else-if="item.ui === UIName.html && item.format"
        v-html="item.format({ form: state.form , initData: props.initData})">
    </div>
    <div v-else-if="item.ui === UIName.link">
        <a :href="state.form[item.key]" target="_blabk" style="color: var(--el-color-primary);">{{ state.form[item.key] }}</a>
    </div>
    <template v-else-if="item.ui === UIName.img">
        <el-image
            style="width: 30px; height: 30px; display: block;border-radius: 4px;margin: 0 auto;"
            :src="state.form[item.key]"
            :z-index="9"
            :zoom-rate="1.2"
            :max-scale="1"
            :min-scale="0.2"
            preview-teleported
            :preview-src-list="[state.form[item.key]]"
            fit="cover"
            />
    </template>
    <template v-else-if="item.ui === UIName.render">
        <Render
            :item="item"
            :items="props.items"
            :form="state.form"
            :initData="initData">
        </Render>
    </template>
</template>
<script lang="ts">
// 内置UI组件
export enum UIName {
    input = 'input',
    inputNumber = 'input-number',
    inputLink = 'input-link',
    cellTextarea = 'cell-textarea',
    cellUpload = 'cell-upload',
    cellRichEditor = 'cell-rich-editor',
    select = 'select',
    checkbox = 'checkbox',
    selectRemote = 'select-remote',
    daterange = 'daterange',
    datetimerange = 'datetimerange',
    datetime = 'datetime',
    date = 'date',
    button = 'button',
    html = 'html',
    link = 'link',
    img = 'img',
    buttonGroup = 'button-group',
    tab = 'tab',
    render = 'render'
}
</script>

<script setup lang="ts">
import { computed, onBeforeMount, reactive, watch } from 'vue'
import { isFunc } from './utils'
import Render from './Render';
import InputLink from './InputLink.vue';
import CellTextarea from './CellTextarea.vue';
import CellUpload from './CellUpload.vue';
import CellRichEditor from './CellRichEditor.vue';

const emits = defineEmits(['event'])

const props = defineProps({
    initData: {
        type: Object,
        default: () => ({})
    },
    item: {
        type: Object,
        default: () => ({})
    },
    form: {
        type: Object,
        default: () => ({})
    },
    items: {
        type: Array,
        default: () => [],
    },
    forwardRef: {
        type: Function,
        default: () => {}
    },
    checkboxPadding: Boolean
})

const state = reactive({
    form: {} as any,
    item: {} as any
})

const _placeholder = computed(() => {
    // const isInputType = ['input', 'input-number'].includes(props.item.ui)
    // return `${isInputType ? '请输入' : '请选择'}${props.item.label}`
    return ''
})

watch(() => props.form, (newVal, oldVal) => {
    state.form = newVal
}, {deep: true})

onBeforeMount(() => {
    state.form = props.form
    state.item = props.item
})

const handleEvent = ({item, eventName}: any) => {
    emits('event', {item, form: state.form, eventName})
}
</script>

<style lang="scss" scoped>
.textAlignLeft{
    :deep(.el-input__inner) {
        text-align: left !important;
    }
    :deep(.el-input__wrapper) {
        padding-left: 11px;
        padding-right: 11px;
    }
}
</style>